Skip to content

Playwright further extend test coverage over contributor discussions forum threads #6638

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Apr 30, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -1,6 +1,10 @@
import re
from playwright.sync_api import Page
from playwright_tests.core.utilities import Utilities
from playwright_tests.pages.contribute.contribute_pages.contributor_discussions.\
delete_thread_post_page import DeleteThreadPostPage
from playwright_tests.pages.contribute.contribute_pages.contributor_discussions.\
edit_thread_post_page import EditThreadPostPage
from playwright_tests.pages.contribute.contribute_pages.contributor_discussions.\
edit_thread_title_page import EditThreadTitle
from playwright_tests.pages.contribute.contribute_pages.contributor_discussions\
Expand All @@ -18,6 +22,8 @@ def __init__(self, page: Page):
self.forum_discussions_page = ForumDiscussionsPage(page)
self.forum_thread_page = ForumThreadPage(page)
self.edit_thread_title_page = EditThreadTitle(page)
self.edit_post_page = EditThreadPostPage(page)
self.delete_thread_post_page = DeleteThreadPostPage(page)

def post_a_new_thread(self, thread_title: str, thread_body: str, cancel=False) -> str:
"""
Expand Down Expand Up @@ -59,6 +65,17 @@ def post_thread_reply(self, reply_body: str) -> str:

return re.search(r'post-(\d+)', self.utilities.get_page_url()).group(1)

def quote_thread_post(self, post_id: str) -> str:
"""
Quote a thread post.
Args:
post_id (str): The ID of the post to be quoted.
"""
self.forum_thread_page.click_on_quote_option(post_id)
self.forum_thread_page.click_on_post_reply_button()

return re.search(r'post-(\d+)', self.utilities.get_page_url()).group(1)

def edit_thread_title(self, new_title: str):
"""
Edit the title of a thread.
Expand All @@ -69,6 +86,34 @@ def edit_thread_title(self, new_title: str):
self.edit_thread_title_page.fill_into_thread_title_input_field(new_title)
self.edit_thread_title_page.click_on_update_thread_button()

def edit_thread_post(self, post_id: str, new_thread_post: str):
"""
Edit the thread post.
Args:
post_id (str): The ID of the post to be edited.
new_thread_post (str): The new post for the thread.
"""
self.forum_thread_page.click_on_edit_this_post_option(post_id)
self.edit_post_page.add_text_inside_the_edit_post_textarea(new_thread_post)
self.edit_post_page.click_on_update_post_button()

def delete_thread_post(self, post_id: str):
"""
Delete a thread post.
Args:
post_id (str): The ID of the post to be deleted.
"""
self.forum_thread_page.click_on_delete_this_post_option(post_id)
self.delete_thread_post_page.click_on_delete_button()

def report_thread_post(self, post_id: str):
"""
Report a thread post.
Args:
post_id (str): The ID of the post to be reported.
"""
self.forum_thread_page.click_on_report_abuse_option(post_id)

def delete_thread(self):
"""
Delete a thread.
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
from playwright_tests.core.basepage import BasePage


class DeleteThreadPostPage(BasePage):
"""
This class contains the locators and actions for the Delete Thread Post page.
"""

def __init__(self, page):
super().__init__(page)
self.delete_page_header = page.locator("article#confirm-delete h1")
self.delete_button = page.locator("//input[@type='submit']")
self.cancel_option = page.get_by_role("link", name="Cancel")

def click_on_delete_button(self):
"""
Click on the 'Delete' button.
"""
self._click(self.delete_button)
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
from playwright_tests.core.basepage import BasePage


class EditThreadPostPage(BasePage):
"""
This class contains the locators and actions for the Edit Thread Post page.
"""
def __init__(self, page):
super().__init__(page)
self.edit_post_header = page.locator("div#edit-post h1")
self.edit_post_textarea = page.locator("textarea#id_content")
self.edit_post_cancel_button = page.get_by_role("link", name="Cancel")
self.edit_post_update_post_button = page.get_by_role("button", name="Update post")
self.edit_post_preview_button = page.get_by_role("button", name="Preview")

def add_text_inside_the_edit_post_textarea(self, text: str):
"""
Add text inside the edit post textarea.
Args:
text (str): The text to be added inside the edit post textarea.
"""
self._fill(self.edit_post_textarea, text)

def click_on_update_post_button(self):
"""
Click on the 'Update post' button.
"""
self._click(self.edit_post_update_post_button)
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
from datetime import datetime
import re
from playwright_tests.core.basepage import BasePage
from playwright_tests.core.utilities import Utilities

Expand Down Expand Up @@ -56,24 +57,38 @@ def __init__(self, page):
self.post_content = lambda post_id: page.locator(
f"//li[@id='post-{post_id}']//div[@class='content']/p")
self.thread_post = lambda post_id: page.locator(f"li#post-{post_id}")
self.thread_post_by_content = lambda post_content: page.locator(
f"//div[@class='content']/p[normalize-space(text())='{post_content}']")
self.modified_by = lambda post_id: page.locator(f"li#post-{post_id} p.text-body-sm")
self.quoted_thread_post_mention = lambda post_id: page.locator(
f"li#post-{post_id} div.content em")
self.quoted_thread_post_mention_link = lambda post_id: page.locator(
f"li#post-{post_id} div.content em a")
self.quoted_thread_post_quote = lambda post_id: page.locator(
f"li#post-{post_id} div.content blockquote")

# Thread post more options locators
self.post_3_dotted_menu = lambda post_id: page.locator(f"li#post-{post_id}").get_by_role(
"button", name="more options")
self.post_3_dotted_menu_expanded = lambda post_id: page.locator(
f"//li[@id='post-{post_id}']//ul[contains(@id,'expand-datahasdropdown')]")
self.private_message = lambda post_id: page.locator(
f"li#post-{post_id} li.mzp-c-menu-list-item").get_by_role(
"link", name="Private message")
self.post_edit_this_post = lambda post_id: page.locator(
f"li#post-{post_id} ul#expand-expand-datahasdropdown-0 li").get_by_role(
f"li#post-{post_id} li.mzp-c-menu-list-item").get_by_role(
"link", name="Edit this post")
self.delete_this_post = lambda post_id: page.locator(
f"li#post-{post_id} ul#expand-expand-datahasdropdown-0 li").get_by_role(
f"li#post-{post_id} li.mzp-c-menu-list-item").get_by_role(
"link", name="Delete this post")
self.quote_this_post = lambda post_id: page.locator(
f"li#post-{post_id} ul#expand-expand-datahasdropdown-0 li").get_by_role(
f"li#post-{post_id} li.mzp-c-menu-list-item").get_by_role(
"link", name="Quote")
self.report_this_post = lambda post_id: page.locator(
f"li#post-{post_id} ul#expand-expand-datahasdropdown-0 li").get_by_role(
f"li#post-{post_id} li.mzp-c-menu-list-item").get_by_role(
"link", name="Report Abuse")
self.link_this_post = lambda post_id: page.locator(
f"li#post-{post_id} ul#expand-expand-datahasdropdown-0 li").get_by_role(
f"li#post-{post_id} li.mzp-c-menu-list-item").get_by_role(
"link", name="Link to this post")

# Post a reply locators
Expand Down Expand Up @@ -118,6 +133,26 @@ def is_thread_post_visible(self, post_id: str) -> bool:
"""
return self._is_element_visible(self.thread_post(post_id))

def is_thread_post_by_name_visible(self, post_name: str) -> bool:
"""
Check if a specific thread post by name is visible.
Args:
post_name (str): The name of the post.
Returns:
bool: True if the post is visible, False otherwise.
"""
return self._is_element_visible(self.thread_post_by_content(post_name))

def get_modified_by_text(self, post_id: str) -> str:
"""
Get the modified by text for a specific post.
Args:
post_id (str): The ID of the post.
Returns:
str: The modified by text.
"""
return self._get_text_of_element(self.modified_by(post_id))

def is_edit_thread_title_option_visible(self) -> bool:
"""
Check if the edit thread title option is visible.
Expand Down Expand Up @@ -299,3 +334,140 @@ def click_on_contributor_discussions_side_navbar_item(self, item_name: str):
item_name (str): The name of the item to click on.
"""
self._click(self.contributor_discussions_side_navbar_item(item_name))

def click_on_3_dotted_menu(self, post_id: str):
"""
Click on the 3-dotted menu for a specific post.
Args:
post_id (str): The ID of the post.
"""
self._click(self.post_3_dotted_menu(post_id),
expected_locator=self.post_3_dotted_menu_expanded(post_id))

def click_on_edit_this_post_option(self, post_id: str):
"""
1. Click on the "Edit this post" option for a specific post.
2. Click on the "Edit this post" option in the 3-dotted menu of the post.
Args:
post_id (str): The ID of the post.
"""
self.click_on_3_dotted_menu(post_id)
self._click(self.post_edit_this_post(post_id))

def is_edit_this_post_option_displayed(self, post_id: str):
"""
Check if the "Edit this post" option is displayed in the 3-dotted menu of a specific post.
Args:
post_id (str): The ID of the post.
Returns:
bool: True if the option is displayed, False otherwise.
"""
self.click_on_3_dotted_menu(post_id)
return self._is_element_visible(self.post_edit_this_post(post_id))

def is_delete_this_post_option_displayed(self, post_id: str):
"""
Check if the "Delete this post" option is displayed in the 3-dotted menu of a specific
post.
Args:
post_id (str): The ID of the post.
Returns:
bool: True if the option is displayed, False otherwise.
"""
self.click_on_3_dotted_menu(post_id)
return self._is_element_visible(self.delete_this_post(post_id))

def click_on_quote_option(self, post_id: str):
"""
Click on the "Quote" option for a specific post.
Args:
post_id (str): The ID of the post.
"""
self.click_on_3_dotted_menu(post_id)
self._click(self.quote_this_post(post_id))

def click_on_delete_this_post_option(self, post_id: str):
"""
Click on the "Delete this post" option for a specific post.
Args:
post_id (str): The ID of the post.
"""
self.click_on_3_dotted_menu(post_id)
self._click(self.delete_this_post(post_id))

def click_on_private_message_option(self, post_id: str):
"""
Click on the "Private message" option for a specific post.
Args:
post_id (str): The ID of the post.
"""
self.click_on_3_dotted_menu(post_id)
self._click(self.private_message(post_id))

def is_quote_option_displayed(self, post_id: str) -> bool:
"""
Check if the "Quote" option is displayed in the 3-dotted menu of a specific post.
Returns:
bool: True if the option is displayed, False otherwise.
"""
self.click_on_3_dotted_menu(post_id)
return self._is_element_visible(self.quote_this_post(post_id))

def click_on_report_abuse_option(self, post_id: str):
"""
Click on the "Report Abuse" option for a specific post.
Args:
post_id (str): The ID of the post.
"""
self.click_on_3_dotted_menu(post_id)
self._click(self.report_this_post(post_id))

def click_on_link_to_this_post_option(self, post_id: str) -> str:
"""
Click on the "Link to this post" option for a specific post.
Args:
post_id (str): The ID of the post.
Returns:
str: The ID of the post.
"""
self.click_on_3_dotted_menu(post_id)
self._click(self.link_this_post(post_id))

return re.search(r'post-(\d+)', self.utilities.get_page_url()).group(1)

def is_report_abuse_option_displayed(self, post_id: str) -> bool:
"""
Check if the "Report Abuse" option is displayed in the 3-dotted menu of a specific post.
Args:
post_id (str): The ID of the post.
Returns:
bool: True if the option is displayed, False otherwise.
"""
self.click_on_3_dotted_menu(post_id)
return self._is_element_visible(self.report_this_post(post_id))

def get_thread_post_mention_text(self, post_id: str) -> str:
"""
Get the thread post mention text for a specific post.
Args:
post_id (str): The ID of the post.
Returns:
str: The thread post mention text.
"""
return self._get_text_of_element(self.quoted_thread_post_mention(post_id))

def click_on_post_mention_link(self, post_id: str):
"""
Click on the post mention link.
"""
self._click(self.quoted_thread_post_mention_link(post_id))

def get_thread_post_quote_text(self, post_id: str) -> str:
"""
Get the thread post quote text for a specific post.
Args:
post_id (str): The ID of the post.
Returns:
str: The thread post quote text.
"""
return self._get_text_of_element(self.quoted_thread_post_quote(post_id))
6 changes: 6 additions & 0 deletions playwright_tests/pages/sumo_pages.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,10 @@
from playwright_tests.pages.common_elements.common_web_elements import CommonWebElements
from playwright_tests.pages.contribute.contribute_pages.contributor_discussions.\
contributor_discussions_page import ContributorDiscussionPage
from playwright_tests.pages.contribute.contribute_pages.contributor_discussions.\
delete_thread_post_page import DeleteThreadPostPage
from playwright_tests.pages.contribute.contribute_pages.contributor_discussions.\
edit_thread_post_page import EditThreadPostPage
from playwright_tests.pages.contribute.contribute_pages.contributor_discussions.\
edit_thread_title_page import EditThreadTitle
from playwright_tests.pages.contribute.contribute_pages.contributor_discussions.\
Expand Down Expand Up @@ -202,6 +206,8 @@ def __init__(self, page: Page):
self.forum_discussions_page = ForumDiscussionsPage(page)
self.new_thread_page = NewThreadPage(page)
self.edit_thread_title_page = EditThreadTitle(page)
self.edit_post_thread_page = EditThreadPostPage(page)
self.delete_thread_post_page = DeleteThreadPostPage(page)
self.forum_thread_page = ForumThreadPage(page)

# Discussion Threads flow.
Expand Down
Loading